﻿//////////////////////////////////////////////////////////////////////////////
//
//  Copyright © 1998-2024 Glodon Company Limited.  All rights reserved.
//
//  Use of this software is subject to the terms of the Glodon license
//  agreement provided at the time of installation or download, or which
//  otherwise accompanies this software in either electronic or hard copy form.  
//
//////////////////////////////////////////////////////////////////////////////


#pragma once

#include "GcmpCommandAction.h"
#include "IActionRequest.h"
#include "IAction.h"
#include "IUiView.h"
#include "IActionUiBehavior.h"

namespace gcmp
{
    class IUiView;
    class Vector3d;
    class IPickEventHandler;
    enum class CursorType : int32_t;

    /// \brief 拾取图形节点命令option
    struct GCMP_COMMAND_ACTION_EXPORT PickNodeReferenceOption
    {
        typedef std::function<void(IUiView*, const gcmp::Vector3d&)> MoveCallback;
        typedef std::function<bool(int, IUiView*, const gcmp::Vector3d&)> OnKeyDownCallback;

        /// \brief 构造函数
        PickNodeReferenceOption(): isMoveAllowed(true), isPickingHighlightOnlyGraphicsNodeAllowed(false), cursorType(CursorType::ArrowCursor), 
            moveCallback(nullptr), pPostEventHandler(nullptr), bMultiSelect(false), isPickNullReturnPos(false), pickedPos(nullptr), FinishedMode(ActionFinishedMode::LButtonDown),
            pickPixelTolerance(-1), isPickElementShapeHandle(false), keyDownCallback(nullptr) {}

        /// \brief 设置是否允许移动
        /// 
        /// \param value true为允许，false为不允许
        /// \return option对象
        PickNodeReferenceOption& SetIsMoveAllowed(bool value) { isMoveAllowed = value; return *this; }

        /// \brief 设置是否拾取只在HighLighted状态下可见的图形节点
        /// 
        /// \param value true为允许，false为不允许
        /// \return option对象
        PickNodeReferenceOption& SetIsPickingHighlightOnlyGraphicsNodeAllowed(bool value) { isPickingHighlightOnlyGraphicsNodeAllowed = value; return *this; }

        /// \brief 设置鼠标移动时的回调函数
        /// 
        /// \param value 回调函数
        /// \return option对象
        PickNodeReferenceOption& SetCursorType(CursorType value) { cursorType = value; return *this; }

        /// \brief 设置鼠标移动时的回调函数
        /// 
        /// \param value 回调函数
        /// \return option对象
        PickNodeReferenceOption& SetMoveCallback(MoveCallback value){ moveCallback = value; return *this;}

        /// \brief 设置键盘按钮按下时的回调函数
        /// 
        /// \param value 回调函数
        /// \return option对象
        PickNodeReferenceOption& SetOnKeyDownCallback(OnKeyDownCallback value) { keyDownCallback = value; return *this; }

        /// \brief 设置拾取完成时的事件handler
        /// 
        /// \param value handler
        /// \return option对象
        PickNodeReferenceOption& SetPostEventHandler(IPickEventHandler* value){ pPostEventHandler = value; return *this;}

        /// \brief 设置是否多选
        /// 
        /// \param value true为多选，false为单选
        /// \return option对象
        PickNodeReferenceOption& SetMultiSelect(bool value) {bMultiSelect = value; return *this;}

        /// \brief 设置没有选中时结束命令还是继续拾取
        /// 
        /// \param value 为true的时候，没有拾取到就结束命令，并返回拾取点在草图平面的坐标; 为false的时候，没有拾取到就继续拾取，直到拾取到才结束命令
        /// \param pPickedPos 草图平面的点
        /// \return option对象
        PickNodeReferenceOption& SetPickNullReturnPos(bool value, Vector3d* pPickedPos) {isPickNullReturnPos = value; pickedPos = pPickedPos; return *this;}

        /// \brief 设置鼠标提示信息
        /// 
        /// \param value 提示信息
        /// \return option对象
        PickNodeReferenceOption& SetMouseTooltipMessage(const std::wstring& value) { mouseTooltipMessage = value; return *this; }

        /// \brief 设置拾取的结束方式
        /// 
        /// \param finishedMode 结束方式，默认左键
        /// \return option对象
        PickNodeReferenceOption& SetFinishedMode(ActionFinishedMode finishedMode) {FinishedMode = finishedMode; return *this;}

        /// \brief 设置交互请求
        /// 
        /// \param value 交互请求
        /// \return option对象
        PickNodeReferenceOption& PostRequest(OwnerPtr<IActionRequest> pRequest) { opRequest = TransferOwnership(pRequest); return *this; }

        /// \brief 设置拾取像素容差
        /// 
        /// \param tolerance 像素容差
        /// \return option对象
        PickNodeReferenceOption& SetPickPixelTolerance(int tolerance) { pickPixelTolerance = tolerance; return *this; }

        /// \brief 设置是否拾取辅助对象
        /// 
        /// \param value 设置为true的时候, 可通过PickNodeReferenceExchangeData获取拾取到的辅助对象Id; 为false的时候, 无法获取辅助对象的Id
        /// \return option对象
        PickNodeReferenceOption& SetPickElementShapeHandle(bool value) { isPickElementShapeHandle = value; return *this; }

        /// \brief 设置创建UI的行为
        /// 
        /// \param opActionUiBehavior 设置自定义的UI行为，不设置时使用平台默认行为。
        /// \return option对象
        PickNodeReferenceOption& SetActionUiBehavior(OwnerPtr<IActionUiBehavior> opActionUiBehavior) { opUiBehavior = TransferOwnership(opActionUiBehavior); return *this; }

        /// 是否允许拖拽
        bool isMoveAllowed;

        /// 是否拾取辅助对象
        bool isPickElementShapeHandle;

        /// 是否拾取只在HighLighted状态下可见的图形节点
        bool isPickingHighlightOnlyGraphicsNodeAllowed;
      
        /// 鼠标样式
        CursorType cursorType;

        /// 鼠标移动时的回调函数
        MoveCallback moveCallback;

        /// 键盘按钮按下时的回调函数
        OnKeyDownCallback keyDownCallback;

        /// 拾取完成时的事件handler
        IPickEventHandler* pPostEventHandler;

        /// 是否多选
        bool bMultiSelect;

        /// 没有拾取到时是否结束命令标志
        bool isPickNullReturnPos;

        /// 没有拾取到的时候结束的话，返回的草图平面的点
        Vector3d* pickedPos;

        /// 鼠标提示信息
        std::wstring mouseTooltipMessage;

        /// 交互请求
        OwnerPtr<IActionRequest> opRequest;

        ///结束模式
        ActionFinishedMode FinishedMode;

        int pickPixelTolerance;

        ///创建UI行为
        OwnerPtr<IActionUiBehavior> opUiBehavior;
    };
}




